home *** CD-ROM | disk | FTP | other *** search
- Path: nntp.nta.no!usenet
- From: torbjorn.sund@fou.telenor.no (Torbj°rn Sund)
- Newsgroups: comp.lang.modula2
- Subject: Re: Reading Floppies.
- Date: 6 Feb 1996 11:12:06 GMT
- Organization: Telenor R&D, Troms°, Norway
- Distribution: world
- Message-ID: <4f7d26$bmh@nntp.nta.no>
- References: <1996Feb1.125721.18589@ucl.ac.uk>
- Reply-To: torbjorn.sund@fou.telenor.no (Torbj°rn Sund)
- NNTP-Posting-Host: grim.tft.tele.no
- X-Newsreader: IBM NewsReader/2 v1.9d - NLS
-
- In <1996Feb1.125721.18589@ucl.ac.uk>, zcaccau@cs.ucl.ac.uk (Chris Austin) writes:
- >
- >In modula-2 is there any way that you can determine whether a floppy drive
- >currently contains a disk and whether it is correctly formatted, (i.e.
- >whether the drive is readable), without getting the DOS abort, retry or
- >ignore message. I would like this to work with CD's, IOMEGA ZipDrives,
- >etc... as well.
-
- Here's an extract of my low-level BIOS and diskette access code.
- All in Modula-2 (sort of), no assembler.
- Note I have extracted only relevant portions,
- complain to me if I missed something out.
- Written for Topspeed M2, but all the non-standard constructs
- have similar counterparts in the other DOS compilers.
- (and I've seen most under DOS).
-
- The idea of reading from the diskette to detect if it is present
- is taken from a fast multitasking diskette copier supplied
- in source with the full JPI M2 distribution. The code is mine
- so there should be no copyright problems, but credit to
- JPI anyway.
-
- Hope this helps.
-
- Cut here:
- - - - - - -
- DEFINITION MODULE BIOSFun;
-
- CONST
- MaxBytesInSector = 1024;
-
- (* following are direct mappings from BIOS functions *)
-
- PROCEDURE ResetDisk( DrvNo: SHORTCARD): SHORTCARD;
- PROCEDURE ReadSectors( DrvNo: SHORTCARD;
- VAR Buffer: ARRAY OF SHORTCARD; VAR NoSec: SHORTCARD;
- HedNo, CylNo, SecNo: SHORTCARD): SHORTCARD;
-
- END BIOSFun.
-
- -- and here --
-
- IMPLEMENTATION MODULE BIOSFun;
-
- (* Interrupt 13H, chosen functions for diskett *)
-
- IMPORT SYSTEM, Lib;
- (*%T _XTD *) (* if compiled with extended (protected) memory model *)
- IMPORT TSXLIB;
- (*%E *)
-
- CONST Int13 = 013H;
-
- (* function 0 *)
- PROCEDURE ResetDisk( DrvNo: SHORTCARD): SHORTCARD;
- VAR
- r: SYSTEM.Registers;
- BEGIN
- r.AH := 0; r.DL := DrvNo;
- Lib.Intr( r, Int13);
- RETURN r.AH;
- END ResetDisk;
-
- (* function 02 *)
- PROCEDURE ReadSectors( DrvNo: SHORTCARD;
- VAR Buffer: ARRAY OF SHORTCARD; VAR NoSec: SHORTCARD;
- HedNo, CylNo, SecNo: SHORTCARD): SHORTCARD;
- VAR
- r: SYSTEM.Registers;
- BEGIN
- WITH r DO
- AH := 2;
- DL := DrvNo;
- AL := NoSec;
- CH := CylNo;
- CL := SecNo;
- DH := HedNo;
- ES := Seg(Buffer);
- BX := Ofs(Buffer);
- Lib.Intr( r, Int13);
- NoSec := AL;
- RETURN AH;
- END;
- END ReadSectors;
-
-
- BEGIN
- (*%T _XTD *)
- TSXLIB.InitInt13();
- (*%E *)
-
- END BIOSFun.
-
- ---- and here ----
-
- DEFINITION MODULE Diskett;
-
- (* Utility functions for diskette *)
- (* Drive number should be 0 and 1 for A: and B:
- if memory serves me right, or maybe it's 1 and 2
- *)
-
- PROCEDURE DiskIsPresent( DrvNo: SHORTCARD): BOOLEAN;
- PROCEDURE Wait4DiskChange( DrvNo: SHORTCARD);
-
- END Diskett.
-
- --- and here ---
-
- IMPLEMENTATION MODULE Diskett;
-
- IMPORT Lib, BIOSFun;
-
- VAR
- DummyBuffer: ARRAY [0 .. BIOSFun.MaxBytesInSector-1] OF SHORTCARD;
-
- PROCEDURE DiskIsPresent( DrvNo: SHORTCARD): BOOLEAN;
- VAR
- SecCnt,
- result : SHORTCARD;
- BEGIN
- IF BIOSFun.ResetDisk( DrvNo) # 0 THEN RETURN FALSE; END;
- SecCnt := 1;
- result := BIOSFun.ReadSectors( DrvNo, DummyBuffer, SecCnt, 0, 0, 1);
- (* yeah, I know, the result codes below should have been changed
- into symbolic constants instead of magic numbers *)
- RETURN (result = 0) OR (result = 2) OR (result = 3) OR (result = 4)
- OR (result = 6) OR (result = 8) OR (result = 9) OR (result = 10H);
- END DiskIsPresent;
-
- PROCEDURE Wait4DiskChange( DrvNo: SHORTCARD);
- VAR
- SecCnt,
- res : SHORTCARD;
- BEGIN
- (* first wait for diskette to be removed *)
- REPEAT
- Lib.Delay(750);
- SecCnt := 1;
- res := BIOSFun.ReadSectors( DrvNo, DummyBuffer, SecCnt, 0, 0, 1);
- UNTIL (res=6);
- (* then wait until a new one is present *)
- WHILE NOT DiskIsPresent( DrvNo) DO Lib.Delay(100); END;
- END Wait4DiskChange;
-
-
- END Diskett.
-
- ---------- cut here
-
- Torbj°rn Sund Telenor R&D
- Tel (+47) 77 61 27 87 Pb 1156, Strandgt 9
- Fax (+47) 77 61 27 02 N-9001 Troms°
- torbjorn.sund@fou.telenor.no Norway
-
-